package ar.edu.itba.pod.legajo48013.event;

import java.rmi.RemoteException;
import java.rmi.server.UnicastRemoteObject;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.concurrent.BlockingQueue;

import ar.edu.itba.event.EventInformation;
import ar.edu.itba.event.RemoteEventDispatcher;
import ar.edu.itba.node.NodeInformation;
import ar.edu.itba.pod.agent.runner.Agent;
import ar.edu.itba.pod.legajo48013.host.Host;

public class RemoteEventDispatcherImpl extends UnicastRemoteObject implements RemoteEventDispatcher{
	
	private static final long serialVersionUID = -5609028095684628803L;

	private Host host;
	public RemoteEventDispatcherImpl(Host host) throws RemoteException{
		this.host = host;
	}

	@Override
	public boolean publish(EventInformation event) throws RemoteException, InterruptedException {
		System.out.println("in " + host.getNode().host() + ":" + host.getNode().port());
		System.out.println(event.nodeId());
		if(host.getProcessedEvents().contains(event) || host.getProcessedEvents().contains(event))
			return false;
		host.addPendingEvent(event);
		System.out.println("adding event ...");
		return true;
	}

	@Override
	public Set<EventInformation> newEventsFor(NodeInformation nodeInformation)
			throws RemoteException {
		List<ProcessedEvent> processedEvents = host.getProcessedEvents();
		Set<EventInformation> newEvents = new HashSet<EventInformation>();
		long lastUpdate = host.getUpdates().get(nodeInformation);
		for(ProcessedEvent pEvent: processedEvents){
			if(lastUpdate < pEvent.getTimestamp()){
				newEvents.add(pEvent.getEvent());
			}
		}
		return newEvents;
	}

	/**
	 * Moves the events queue for an agent between nodes. This method should be
	 * used with AgentsTransfer#stopAndGet, so the agent should be stopped and
	 * moved before its event queue is migrated. Before calling this method a
	 * proper event synchronization between both nodes should be performed in
	 * order to avoid losing events.
	 * 
	 * @param agent
	 *            the agent whose event queue is expected
	 * @return the agent queue for this agent. Never returns null.
	 */
	@Override
	public BlockingQueue<Object> moveQueueFor(Agent agent)
			throws RemoteException {
		// TODO Auto-generated method stub
		return null;
	}

}
